package cuppics;

import java.util.ArrayList;
import java.util.BitSet;
import java.util.List;

import org.junit.Test;

public class Prj10 {

	/**
	 * The sum of the primes below 10 is 2 + 3 + 5 + 7 = 17.
	 * 
	 * Find the sum of all the primes below two million.
	 */
	@Test
	public void test() {
		
		PrimeMaster mt = new PrimeMaster().calcultePrimeList(2000000);
		
		System.out.println(mt.toString());
		System.out.println(mt.sum);
		
		
	}
	
	
	public static class PrimeMaster {

		public List<Integer> primeList = new ArrayList<Integer>();

		
		public Long sum = 0L;
		
		
		public PrimeMaster calcultePrimeList(int upLimit ) {

			primeList.clear();

			BitSet bs = new BitSet(upLimit);

			boolean init = true;

			while (true) {
				int val = getNonSetVal(init, bs, primeList, upLimit);
				init = false;

				for (int i = val + 1; i < upLimit; i++) {
					if (i % val == 0) {
						bs.set(i);
					}
					
				}
				
				System.out.println( " val =" + val);

				if (val < 0) {
					break;
				}
			}

			for (int i = 2; i < upLimit; i++) {

				if (!bs.get(i)) {
					primeList.add(i);
				}
			}

			return this;
		}

		private int getNonSetVal(boolean init, BitSet bs,
				List<Integer> primeList_, int upLimit) {

			if (init) {
				primeList_.add(2);
				bs.set(2);
				return 2;
			}

			for (int i = 3; i < upLimit; i++) {
				if (!bs.get(i)) {
					bs.set(i);
					primeList_.add(i);
					return i;
				}
			}
			return -1;
		}

		@Override
		public String toString() {

			Long sum = 0L;
			StringBuilder sb = new StringBuilder();
			for (int i = 0; i < primeList.size(); i++) {
				if( ( i + 1 ) % 20 == 0){
					sb.append("\n");
				}
				sb.append(primeList.get(i) + ",");
				
				sum = sum + primeList.get(i);
			}
			sb.append("\n");
			

			this.sum = sum;
			return sb.toString();
		}

	}
	
}
